package com.my.esp8266client;

import javax.swing.*;
import javax.swing.border.EmptyBorder;
import javax.swing.border.EtchedBorder;
import javax.swing.event.CaretEvent;
import javax.swing.event.CaretListener;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
import java.io.*;
import java.net.Socket;

public class MainFrame extends JFrame {

    private final JTextArea taRes;
    private final JPanel contentPane;
    private final JTextArea taReq;

    private Socket socket;
    private static final String GET_REQUEST_TEXT =
            "GET /api/param?p=321 HTTP/1.0\n" +
                    "Accept: text/html,application/json,*/*;\n" +
                    "Cache-Control: max-age=0\n" +
                    "Connection: close\n" +
                    "Host: 127.0.0.1\n" +
                    "\n" +
                    "";

    private static final String POST_REQUEST_TEXT =
            "POST /api/param HTTP/1.0\n" +
                    "Accept: text/html,application/json,*/*;\n" +
                    "Cache-Control: max-age=0\n" +
                    "Connection: close\n" +
                    "Content-Type: application/x-www-form-urlencoded\n" +
                    "Content-Length: 5\n" +
                    "Host: 127.0.0.1\n" +
                    "\n" +
                    "p=123";

    public MainFrame() {
        setTitle("模拟ESP8266的HTTP客户端");
        setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        setBounds(100, 100, 640, 480);
        contentPane = new JPanel(new BorderLayout(5, 5));
        contentPane.setBorder(new EtchedBorder(EtchedBorder.LOWERED));
        setContentPane(contentPane);

        JPanel northPane = new JPanel(new FlowLayout(FlowLayout.CENTER, 5, 5));
        contentPane.add(northPane, BorderLayout.NORTH);
        JLabel label1 = new JLabel("服务器域名/IP");
        JTextField ipTf = new JTextField("127.0.0.1");
        ipTf.setColumns(20);
        JLabel label2 = new JLabel("服务器端口");
        JTextField portTf = new JTextField("8080");
        portTf.setColumns(6);
        JButton btnSend = new JButton("发送HTTP请求");

        northPane.add(label1);
        northPane.add(ipTf);
        northPane.add(label2);
        northPane.add(portTf);
        northPane.add(btnSend);

        JSplitPane centerPane = new JSplitPane();
        centerPane.setBorder(new EmptyBorder(5, 5, 5, 5));
        centerPane.setDividerSize(5);
        centerPane.setDividerLocation(this.getWidth() / 2 - 30);

        contentPane.add(centerPane, BorderLayout.CENTER);
        taReq = new JTextArea(GET_REQUEST_TEXT);
        taReq.setBorder(new EmptyBorder(5, 5, 5, 5));
        JScrollPane scrollPane1 = new JScrollPane(taReq);

        JPanel header1 = new JPanel(new FlowLayout(FlowLayout.LEADING, 10, 5));
        header1.add(new JLabel("请求报文"));
        JComboBox<String> comboBox = new JComboBox<>(new String[]{"GET", "POST"});
        header1.add(comboBox);

        header1.add(new JLabel("光标前字符数"));
        JTextField tfLength1 = new JTextField(taReq.getText().length() + "");
        tfLength1.setEditable(false);
        tfLength1.setColumns(6);
        header1.add(tfLength1);
        scrollPane1.setColumnHeaderView(header1);

        taRes = new JTextArea("");
        taRes.setBorder(new EmptyBorder(5, 5, 5, 5));
        JScrollPane scrollPane2 = new JScrollPane(taRes);
        JPanel header2 = new JPanel(new FlowLayout(FlowLayout.LEADING, 5, 5));
        header2.add(new JLabel("响应报文"));
        JButton btnClear = new JButton("清空");
        header2.add(btnClear);

        header2.add(new JLabel("光标前字符数"));
        JTextField tfLength2 = new JTextField(taRes.getText().length() + "");
        tfLength2.setEditable(false);
        tfLength2.setColumns(6);
        header2.add(tfLength2);
        scrollPane2.setColumnHeaderView(header2);
        centerPane.setLeftComponent(scrollPane1);
        centerPane.setRightComponent(scrollPane2);

        btnSend.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                taRes.setText("");
                int port = Integer.parseInt(portTf.getText());
                String ip = ipTf.getText();
                sendRequest(ip, port);
            }
        });

        comboBox.addItemListener(new ItemListener() {
            @Override
            public void itemStateChanged(ItemEvent e) {
                if (e.getItem().equals("GET")) {
                    taReq.setText(GET_REQUEST_TEXT);
                } else if (e.getItem().equals("POST")) {
                    taReq.setText(POST_REQUEST_TEXT);
                }
            }
        });

        btnClear.addActionListener(new ActionListener() {
            @Override
            public void actionPerformed(ActionEvent e) {
                taRes.setText("");
            }
        });

        taReq.addCaretListener(new CaretListener() {
            @Override
            public void caretUpdate(CaretEvent e) {
                tfLength1.setText(e.getDot() + "");
            }
        });
        taRes.addCaretListener(new CaretListener() {
            @Override
            public void caretUpdate(CaretEvent e) {
                tfLength2.setText(e.getDot() + "");
            }
        });

    }

    private void sendRequest(String ip, int port) {
        try {
            socket = new Socket(ip, port);
            BufferedWriter bw = new BufferedWriter(new OutputStreamWriter(socket.getOutputStream(), "UTF-8"));
            BufferedReader br = new BufferedReader(new InputStreamReader(socket.getInputStream(), "UTF-8"));
            String text = taReq.getText();
            bw.write(text);
            bw.flush();
            socket.shutdownOutput();
            String line = null;
            while ((line = br.readLine()) != null) {
                taRes.append(line);
                taRes.append("\r\n");
            }
            bw.close();
            br.close();
            socket.close();
        } catch (IOException e) {
            JOptionPane.showMessageDialog(this, "TCP连接失败，异常：" + e.toString());
            e.printStackTrace();
        }
    }

    public static void main(String[] args) {
        //加载皮肤
        try {
            UIManager.setLookAndFeel(com.sun.java.swing.plaf.windows.WindowsLookAndFeel.class.getName());
        } catch (Exception e) {
            JOptionPane.showMessageDialog(null, "加载皮肤外观错误:" + e);
        }
        new MainFrame().setVisible(true);
    }
}
